#pragma once

#include <Arduino.h>
#include "Screen.h"
#include "Keys.h"
#include "pins_config.h"

// 2048游戏类
class Num2048 {
public:
  // 游戏入口
  void main(Screen &screen, Keys &keys);

private:
  // 游戏常量
  static const int GRID_SIZE = 4;        // 4x4网格
  static const int CELL_SIZE = 52;       // 每个格子的大小
  static const int CELL_PADDING = 4;     // 格子间距
  static const int GRID_OFFSET_X = 5;    // 网格X偏移
  static const int GRID_OFFSET_Y = 160;  // 网格Y偏移

  static const int SCORE_TITLE_X = 5;     // 分数标题 X 位置
  static const int SCORE_TITLE_Y = 4;     // 分数标题 Y 位置
  static const int SCORE_VALUE_X = 5;     // 分数值 x 位置
  static const int SCORE_VALUE_Y = 20;    // 分数值 Y 位置
  static const int BEST_TITLE_X = 120;    // 最高分标题 X 位置
  static const int BEST_TITLE_Y = 4;      // 最高分标题 Y 位置
  static const int BEST_VALUE_X = 120;    // 最高分值 X 位置
  static const int BEST_VALUE_Y = 20;     // 最高分值 Y 位置
  static const int CONTROL_TITLE_X = 5;   // 操作说明 X 位置
  static const int CONTROL_TITLE_Y = 40;  // 操作说明 Y 位置
  static const int CONTROL_VALUE_X = 60;  // 操作说明 X 位置
  static const int CONTROL_VALUE_Y = 40;  // 操作说明 Y 位置

  static const int MOVE_ANIMATION_STEPS = 4;  // 移动动画步数

  // 游戏状态
  enum GameState {
    PLAYING,    // 游戏中
    PAUSED,     // 暂停
    GAME_OVER,  // 游戏结束
    WIN         // 胜利（达到2048）
  };

  // 游戏变量
  GameState state;
  int grid[GRID_SIZE][GRID_SIZE];  // 游戏网格
  unsigned long score;             // 分数
  unsigned long bestScore;         // 最高分
  bool moved;                      // 本回合是否移动过
  bool hasWon;                     // 是否已经获胜过

  unsigned long lastMoveTime;  // 上次移动时间

  // 颜色表（根据数字大小）
  static const uint16_t TILE_COLORS[12];
  static const uint16_t TEXT_COLORS[12];

  // 初始化游戏
  void initGame();

  // 绘制函数
  void drawGameArea(Screen &screen);
  void drawGrid(Screen &screen);
  void drawCell(Screen &screen, int row, int col, int value);
  void drawInfo(Screen &screen);
  void drawPausedMessage(Screen &screen);
  void drawGameOver(Screen &screen);
  void drawWin(Screen &screen);

  // 游戏逻辑
  void addRandomTile();                                 // 添加随机数字（2或4）
  bool move(int direction);                             // 移动（0=上, 1=右, 2=下, 3=左）
  bool canMove();                                       // 检查是否还能移动
  bool hasEmptyCell();                                  // 是否有空格子
  void mergeLine(int line[GRID_SIZE], int &lineScore);  // 合并一行
  void rotateCW();                                      // 顺时针旋转90度
  void rotateCCW();                                     // 逆时针旋转90度

  // 输入处理
  void handleInput(Keys &keys);

  // 工具函数
  uint16_t getTileColor(int value);  // 获取方块颜色
  uint16_t getTextColor(int value);  // 获取文字颜色
  String getValueString(int value);  // 获取数字显示文本
  int log2(int n);                   // 计算log2值
};